<template>
  <div class="gis-container" :class="!visible && 'hide'">
    <div class="tools-bar" v-if="false">
      <!-- <input type="text" v-model="x" />
        <input type="text" v-model="y" />
        <input type="text" v-model="z" />
        <a-button type="primary" @click="setDataSetTransform()">
          模型偏移
        </a-button>-->
      <a-button type="primary" @click="getCamLocate()">
        获取相机方位
      </a-button>
      <a-button type="primary" @click="addFenceByPot()">
        绘制电子围栏
      </a-button>
      <a-button type="primary" @click="editorDrawerVisible = true">
        编辑电子围栏
      </a-button>
    </div>
    <div class="bim-container" id="bim-container">
      <div class="BlackHole-container" ref="blackHoleContainer"></div>
      <!-- 港区位置 -->
      <div
        class="port-location-warp"
        :class="!portLocationShow && 'hide'"
        v-for="({ position, portName, icon, uuid },
        index) in portLocationSource"
        :key="uuid"
        :style="{
          left: position.left + 'px',
          bottom: position.bottom + 'px',
          background: `url(${require(`@/assets/img/portalEntry/${icon}.png`)})`,
        }"
        @click="portLocationClick(portLocationSource[index])"
      >
        <div class="name">{{ portName }}</div>
      </div>
    </div>
    <!--  -->
    <a-spin size="large" :spinning="pageSpinning" class="page-spinning" />
    <!-- 港区集合 v-if="extra != 'EngineeringManage'"-->
    <div
      class="port-area-container"
      v-if="digitalKeyVal == 'PlanningManage' || extra == 'EngineeringManage'"
    >
      <div
        class="port-item"
        :class="[portIndex == 'areaType08' && 'active-port']"
        @click="handlePort('areaType08')"
      >
        <div class="icon"></div>
        <div class="name">
          连云港港区
        </div>
      </div>
      <div
        class="port-item"
        :class="[portIndex == 'areaType07' && 'active-port']"
        @click="handlePort('areaType07')"
      >
        <div class="icon"></div>
        <div class="name">
          赣榆港区
        </div>
      </div>
      <div
        class="port-item"
        :class="[portIndex == 'areaType09' && 'active-port']"
        @click="handlePort('areaType09')"
      >
        <div class="icon"></div>
        <div class="name">
          徐圩港区
        </div>
      </div>
      <div
        class="port-item"
        :class="[portIndex == 'areaType10' && 'active-port']"
        @click="handlePort('areaType10')"
      >
        <div class="icon"></div>
        <div class="name">
          灌河港区
        </div>
      </div>
    </div>

    <!-- 配置管理按钮 -->
    <div
      v-if="extra != 'EngineeringManage'"
      class="config-manage-button"
      :class="[
        configPanel.buttonMenuVisible && 'hide',
        configPanel.panelVisible && 'right',
        sysUIPanelVisible && 'right_2',
      ]"
      @mouseenter="handleConfigBtnMouseEnter"
      @mouseleave="handleConfigMouseLeave"
    >
      配置管理
      <div class="config-menu">
        <div
          class="item"
          :class="configPanel.buttonMenuIndex == 'regionalManage' && 'active'"
          @click="openConfigPanel('regionalManage')"
        >
          区域管理
        </div>
        <div
          class="item"
          :class="configPanel.buttonMenuIndex == 'districtManage' && 'active'"
          @click="openConfigPanel('districtManage')"
        >
          片区绘制
        </div>
        <div
          class="item"
          :class="configPanel.buttonMenuIndex == 'markManage' && 'active'"
          @click="openConfigPanel('markManage')"
        >
          标记管理
        </div>
      </div>
    </div>
    <!-- 码头图列 v-if="extra != 'EngineeringManage'"-->
    <!-- 港区实景 -->
    <!-- 港区管理 -->
    <!-- 项目千里眼 -->

    <!-- <div
      class="dock-plan-warp"
      :class="[
        digitalKey() == 'DynamicMonitor' && 'hide',
        !sysUIPanelVisible && 'right',
        configPanel.panelVisible && 'left',
        extra == 'EngineeringManage' && 'right-max',
      ]"
    >
      <template v-if="digitalKey() == 'LiveAction'">
        <a-row v-for="item in portSoucre" :key="item.uuid">
          <a-col :span="24">
            <a-checkbox v-model="item.select" @change="handlePortChange(item)">
              {{ item.dicItemName }}
            </a-checkbox>
          </a-col>
        </a-row>
      </template>

      <template v-if="digitalKey() == 'PlanningManage'">
        <a-row v-for="item in wharfSoucre" :key="item.uuid">
          <a-col :span="24">
            <a-checkbox v-model="item.select" @change="handlePortChange(item)">
              {{ item.dicItemName }}
            </a-checkbox>
          </a-col>
        </a-row>
      </template>

      <template v-if="digitalKey() == 'DynamicMonitor'">
        <a-row v-for="item in markManage.typeData" :key="item.uuid">
          <a-col :span="24">
            <a-checkbox v-model="item.select" @change="handlePortChange(item)">
              {{ item.dicItemName }}
            </a-checkbox>
          </a-col>
        </a-row>
      </template>
    </div> -->

    <!-- bim工具栏 -->
    <div
      class="bim-tool-bar"
      v-if="extra != 'EngineeringManage' && bimToolBarShow"
      :class="[sysUIPanelVisible && 'show', configPanel.panelVisible && 'hide']"
    >
      工具栏
      <a-switch @change="handleSwitch($event)" />
    </div>
    <!-- 配置管理面板  -->
    <div
      class="config-panel-container"
      :class="configPanel.panelVisible && 'show'"
    >
      <div class="body">
        <div class="header">
          {{ configPanel.buttonMenuIndex | getTitleValue }}
          <div class="close" @click="closeConfigPanel(0)"></div>
        </div>
        <div class="content">
          <components
            :is="configPanel.buttonMenuIndex"
            :ProbeRet="ProbeRet"
            v-if="configPanel.buttonMenuIndex"
            :visible="configPanel.panelVisible"
          ></components>
        </div>
      </div>
    </div>
    <!-- 模型构件列表 v-if="digitalKey() == 'LiveAction'"-->
    <div
      class="elem-list-warp"
      v-if="false"
      :class="!showDataSetTree && 'hide'"
    >
      <div class="visible-button">
        <div
          class="button-item"
          :class="showDataSetTree == 1 && 'active'"
          @click="checkListPannel(1)"
        >
          <span>项目列表</span>
        </div>
        <div
          class="button-item"
          :class="showDataSetTree == 2 && 'active'"
          @click="checkListPannel(2)"
        >
          <span>模型列表</span>
        </div>
      </div>
      <div class="tree-card">
        <!-- 关闭按钮 -->
        <div class="close-button" @click="showDataSetTree = null"></div>
        <div class="header">
          {{ showDataSetTree == 1 ? "项目列表" : "模型列表" }}
        </div>
        <div class="body">
          <div class="condition-warp">
            <!-- 选择区域 -->
            <a-select
              v-model="conditionQueryInfo.areaCode"
              style="width: 160px"
              allowClear
              placeholder="请选择所属区域"
            >
              <a-icon slot="suffixIcon" type="caret-down" />
              <a-select-option value="320701"> 市辖区 </a-select-option>
              <a-select-option value="320703"> 连云区 </a-select-option>
              <a-select-option value="320706"> 海州区 </a-select-option>
              <a-select-option value="320707"> 赣榆区 </a-select-option>
              <a-select-option value="320722"> 东海县 </a-select-option>
              <a-select-option value="320723"> 灌云县 </a-select-option>
              <a-select-option value="320724"> 灌南县 </a-select-option>
            </a-select>
            <!-- 选择项目状态 -->
            <a-select
              v-model="conditionQueryInfo.status"
              style="width: 160px"
              allowClear
              placeholder="请选择项目状态"
              v-if="showDataSetTree == 1"
            >
              <a-icon slot="suffixIcon" type="caret-down" />
              <a-select-option value="1">
                在建
              </a-select-option>
              <a-select-option value="2">
                完工
              </a-select-option>
            </a-select>
            <!-- 选择项目 -->
            <a-select
              style="width: 160px"
              placeholder="请选择所属项目"
              v-if="showDataSetTree == 2"
            >
              <a-icon slot="suffixIcon" type="caret-down" />
            </a-select>
          </div>
          <div class="condition-body">
            <projectList
              v-if="showDataSetTree == 1"
              @changeProPosition="changeProPosition"
            ></projectList>
            <DataSetTree v-if="showDataSetTree == 2"></DataSetTree>
          </div>
        </div>
      </div>
    </div>
    <!-- 左侧菜单 -->
    <div
      class="left-menu-container"
      :class="!leftMenuVisible && 'hide'"
      v-if="extra != 'EngineeringManage'"
    >
      <div class="body">
        <div class="body-container">
          <!-- 图层管理 -->
          <div class="card-container" :class="cardIndex == 0 ? 'show' : 'hide'">
            <div class="card-header">
              项目一张图
              <div class="button" @click="showCard(0)"></div>
            </div>
            <div class="card-content">
              <div class="condition">
                <!-- 所属区域       allowClear-->
                <a-select
                  v-model="layerManage.area"
                  placeholder="请选择所属区域"
                  @change="layerAreaChange($event)"
                >
                  <a-select-option
                    :value="item.dicItemCode"
                    v-for="(item, index) in layerManage.areaData"
                    :key="index"
                  >
                    {{ item.dicItemName }}
                  </a-select-option>
                </a-select>
              </div>
              <div class="condition" style="padding-top: 0">
                <!-- 所属项目 allowClear -->
                <a-select
                  v-model="layerManage.proCode"
                  placeholder="请选择所属项目"
                  @change="layerProjectChange($event)"
                >
                  <a-select-option
                    :value="item.proCode"
                    v-for="item in layerManage.projectData"
                    :key="item.uuid"
                  >
                    {{ item.proName }}
                  </a-select-option>
                </a-select>
              </div>
              <div class="tree-container">
                <a-spin
                  size="large"
                  :spinning="layerManage.loading"
                  class="card-spinning"
                />
                <a-tree
                  v-model="layerManage.checkedKeys"
                  checkable
                  :expanded-keys="layerManage.expandedKeys"
                  :auto-expand-parent="layerManage.autoExpandParent"
                  :selected-keys="layerManage.selectedKeys"
                  :tree-data="layerManage.treeData"
                  @check="handleLayerTreeCheck"
                  @select="handleLayerTreeSelect"
                  @expand="onExpand($event, 'layerManage')"
                  :replaceFields="{
                    children: 'subNodes',
                    title: 'nodeName',
                    key: 'nodeId',
                  }"
                ></a-tree>
              </div>
            </div>
          </div>
          <!-- 三维场景 -->
          <div class="card-container" :class="cardIndex == 4 ? 'show' : 'hide'">
            <div class="card-header">
              三维场景
              <div class="button" @click="showCard(4)"></div>
            </div>
            <div class="card-content">
              <div class="tree-container">
                <a-spin
                  size="large"
                  :spinning="threeManage.loading"
                  class="card-spinning"
                />
                <a-tree
                  v-model="threeManage.checkedKeys"
                  checkable
                  :expanded-keys="threeManage.expandedKeys"
                  :auto-expand-parent="threeManage.autoExpandParent"
                  :selected-keys="threeManage.selectedKeys"
                  :tree-data="threeManage.treeData"
                  @check="handleThreeTreeCheck"
                  @select="handleThreeTreeSelect"
                  @expand="onExpand($event, 'threeManage')"
                  :replaceFields="{
                    children: 'subNodes',
                    title: 'nodeName',
                    key: 'nodeId',
                  }"
                ></a-tree>
              </div>
            </div>
          </div>
          <!-- 片区管理 -->
          <div class="card-container" :class="cardIndex == 1 ? 'show' : 'hide'">
            <div class="card-header">
              片区管理
              <div class="button" @click="showCard(1)"></div>
            </div>
            <div class="card-content">
              <div class="condition">
                <!-- 所属区域 -->
                <a-tree-select
                  v-model="areaManage.area"
                  show-search
                  :dropdown-style="{ maxHeight: '400px', overflow: 'auto' }"
                  placeholder="请选择所属区域"
                  searchPlaceholder="请输入"
                  allow-clear
                  tree-default-expand-all
                  treeNodeFilterProp="title"
                  :replaceFields="{
                    children: 'childs',
                    title: 'name',
                    key: 'uuid',
                    value: 'uuid',
                  }"
                  :tree-data="areaManage.areaData"
                  @change="getAreaTreeList()"
                >
                </a-tree-select>
              </div>
              <div class="condition" style="padding-top: 0">
                <!-- 类型 -->
                <a-select
                  v-model="areaManage.type"
                  placeholder="请选择类型"
                  allowClear
                  @change="getAreaTreeList()"
                >
                  <a-select-option
                    :value="item.dicItemCode"
                    v-for="(item, index) in areaManage.typeData"
                    :key="index"
                  >
                    {{ item.dicItemName }}
                  </a-select-option>
                </a-select>
              </div>
              <div class="tree-container">
                <a-empty
                  :image="simpleImage"
                  v-if="areaManage.treeData.length == 0"
                />
                <a-tree
                  v-model="areaManage.checkedKeys"
                  checkable
                  :expanded-keys="areaManage.expandedKeys"
                  :auto-expand-parent="areaManage.autoExpandParent"
                  :selected-keys="areaManage.selectedKeys"
                  :tree-data="areaManage.treeData"
                  @check="handleTreeCheck"
                  @select="handleTreeSelect"
                  @expand="onExpand($event, 'areaManage')"
                  :replaceFields="{
                    children: 'childs',
                    title: 'name',
                    key: 'uuid',
                  }"
                ></a-tree>
              </div>
            </div>
          </div>
          <!-- 标记管理 -->
          <div class="card-container" :class="cardIndex == 2 ? 'show' : 'hide'">
            <div class="card-header">
              标记管理
              <div class="button" @click="showCard(2)"></div>
            </div>
            <div class="card-content">
              <div class="condition">
                <!-- 所属区域 -->
                <a-tree-select
                  v-model="markManage.area"
                  show-search
                  :dropdown-style="{ maxHeight: '400px', overflow: 'auto' }"
                  placeholder="请选择所属区域"
                  searchPlaceholder="请输入"
                  allow-clear
                  tree-default-expand-all
                  treeNodeFilterProp="title"
                  :replaceFields="{
                    children: 'childs',
                    title: 'name',
                    key: 'uuid',
                    value: 'uuid',
                  }"
                  :tree-data="areaManage.areaData"
                  @change="getMarkTreeList()"
                >
                </a-tree-select>
              </div>
              <div class="condition" style="padding-top: 0">
                <!-- 类型 -->
                <a-select
                  v-model="markManage.type"
                  allowClear
                  placeholder="请选择类型"
                  @change="getMarkTreeList()"
                >
                  <a-select-option
                    :value="item.dicItemCode"
                    v-for="(item, index) in markManage.typeData"
                    :key="index"
                  >
                    {{ item.dicItemName }}
                  </a-select-option>
                </a-select>
              </div>
              <div class="tree-container">
                <a-empty
                  :image="simpleImage"
                  v-if="markManage.treeData.length == 0"
                />
                <a-tree
                  v-model="markManage.checkedKeys"
                  checkable
                  :expanded-keys="markManage.expandedKeys"
                  :auto-expand-parent="markManage.autoExpandParent"
                  :selected-keys="markManage.selectedKeys"
                  :tree-data="markManage.treeData"
                  @check="handleTreeCheck"
                  @select="handleTreeSelect"
                  @expand="onExpand($event, 'markManage')"
                  :replaceFields="{
                    children: 'childs',
                    title: 'name',
                    key: 'uuid',
                  }"
                ></a-tree>
              </div>
            </div>
          </div>
        </div>
        <div
          class="open-button"
          :class="!leftMenuVisible && 'hide'"
          @click="openLeftMenu()"
        ></div>
      </div>
    </div>
    <!-- 动态监测图列 -->
    <div
      class="monitor-legend"
      v-if="false"
      :class="digitalKey() != 'DynamicMonitor' && 'hide'"
    >
      <div class="legend-item">球机</div>
      <div class="legend-item">枪机</div>
      <div class="legend-item">工程项目</div>
    </div>
    <!-- 摄像头树列表弹窗 v-if="digitalKey() == 'DynamicMonitor'"-->
    <div class="elem-list-warp" v-if="false" :class="!cameraTree && 'hide'">
      <div class="visible-button">
        <div
          class="button-item"
          :class="cameraTree == 1 && 'active'"
          @click="checkListPannel(1)"
        >
          <span>项目列表</span>
        </div>
      </div>
      <div class="tree-card">
        <!-- 关闭按钮 -->
        <div class="close-button" @click="cameraTree = null"></div>
        <div class="header">
          项目列表
        </div>
        <div class="body">
          <div class="condition-body">
            <cameraList></cameraList>
          </div>
        </div>
      </div>
    </div>

    <!-- 蒙层 -->
    <div class="gis-layer-bg"></div>
    <!-- 港口规划图弹窗 -->
    <PortAreaPlanModal
      :visible.sync="portImgVisible"
      :source="currenPortSource"
    ></PortAreaPlanModal>
    <!-- 监控弹窗 -->
    <VideoModal
      :visible.sync="videoModalVisible"
      :ancUUID="ancUUID"
    ></VideoModal>
    <!--  -->
    <ProjectDetailModal
      :visible.sync="projectDetailVisible"
      :ancUUID="ancUUID"
    ></ProjectDetailModal>
    <!-- <components :is="componentKey" :visible="componentVisible"></components> -->
    <!-- 编辑弹窗 -->
    <CustomEditorDrawer
      ref="customEditorDrawer"
      :visible.sync="editorDrawerVisible"
      :portSource="portLocationSource"
      :gisData="gisData"
    >
    </CustomEditorDrawer>
    <!-- 项目进度 -->
    <projectSchedule v-if="extra == 'EngineeringManage'"></projectSchedule>
    <rightStatistics v-if="extra == 'EngineeringManage'"></rightStatistics>
  </div>
</template>
<script>
import { axios } from "@/utils/request";
import { mapGetters } from "vuex";
// import { canvasHolder } from "@/blackHole/CanvasHolder";
import cloneDeep from "lodash.clonedeep";
import { addAttributeByKey, flatTreeData } from "@/utils/util.js";
//港区实景
import LiveAction from "./liveAction";
//规划管理
import PlanningManage from "./planningManage";
//动态监测
import DynamicMonitor from "./dynamicMonitor";
//模型列表
import DataSetTree from "./dataSetTree";
//项目列表
import projectList from "./projectList";
//港口规划图弹窗
import PortAreaPlanModal from "./portAreaPlanModal";
//监控弹窗
import VideoModal from "./videoModal";
//项目详情弹窗
import ProjectDetailModal from "./projectDetailModal";
//编辑抽屉弹窗
import CustomEditorDrawer from "./customEditorDrawer";
//摄像头列表
import cameraList from "./cameraList";
//区域管理
import regionalManage from "./components/regionalManage";
//片区管理
import districtManage from "./components/districtManage";
//标记管理
import markManage from "./components/markManage";
//项目进度
import projectSchedule from "../engineeringManage/projectSchedule";
import rightStatistics from "../engineeringManage/rightStatistics";
import { Empty } from "ant-design-vue";
import { EventBus } from "@/utils/eventBus";

import { canvasHolder } from "@/blackHoleTools/CanvasHolder";
import { releaseEngine, initialSDKModule } from "@/blackHoleTools/Engine";
export default {
  inject: ["digitalKey"],
  name: "GIS",
  props: {
    extra: {
      type: String,
      default: "",
    },
    visible: {
      type: Boolean,
      default: true,
    },
  },
  components: {
    LiveAction,
    PlanningManage,
    DynamicMonitor,
    DataSetTree,
    PortAreaPlanModal,
    VideoModal,
    ProjectDetailModal,
    CustomEditorDrawer,
    projectList,
    cameraList,
    regionalManage,
    districtManage,
    markManage,
    projectSchedule,
    rightStatistics,
  },
  computed: {
    // ...mapGetters(["RESystemRenderReady"]),
    ...mapGetters(["blackHoleAssetsPreFetch", "blackHoleRESystemCreated"]),
    digitalKeyVal() {
      return this.digitalKey();
    },
  },
  filters: {
    getTitleValue(val) {
      switch (val) {
        case "regionalManage":
          return "区域管理";

        case "districtManage":
          return "片区管理";

        case "markManage":
          return "标记管理";

        default:
          break;
      }
    },
  },
  watch: {
    // //系统引擎创建完成 && 公共资源加载完成
    // RESystemRenderReady: {
    //   handler(val) {
    //     if (val == true) {
    //       this.$nextTick((_) => {
    //         this.addEventListener();
    //         this.onEngineCreated();
    //       });
    //     }
    //   },
    //   immediate: true,
    // },

    blackHoleAssetsPreFetch: {
      handler(val) {
        this.$nextTick((_) => {
          if (val) {
            initialSDKModule();
          }
        });
      },
      immediate: true,
    },

    blackHoleRESystemCreated: {
      handler(val) {
        if (val) {
          this.$nextTick((_) => {
            this.addEventListener();
            this.onEngineCreated();
          });
        }
      },
      immediate: true,
    },

    digitalKeyVal: {
      handler(val) {
        switch (val) {
          case "LiveAction":
            this.portSoucre.forEach((v) => {
              v.select = true;
            });
            this.cardIndex = 0;
            break;

          case "PlanningManage":
            this.wharfSoucre.forEach((v) => {
              v.select = true;
            });
            this.cardIndex = 1;
            break;

          case "DynamicMonitor":
            this.markManage.typeData.forEach((v) => {
              v.select = true;
            });
            this.cardIndex = 2;
            break;

          default:
            break;
        }
      },
    },
  },
  data() {
    return {
      treeSelectFlag: false,
      cardIndex: 0,
      bimToolBarShow: true,
      ancUUID: "",
      bimLayerSource: [],
      ygDataSetId: "",
      pageSpinning: false,
      //图层管理
      layerManage: {
        //所属区域
        area: undefined,
        areaData: [],
        //所属项目
        proCode: undefined,
        projectData: [],
        treeData: [],
        expandedKeys: [],
        autoExpandParent: false,
        checkedKeys: [],
        selectedKeys: [],
        loading: false,
      },
      //三维场景管理
      threeManage: {
        treeData: [],
        expandedKeys: [],
        autoExpandParent: false,
        checkedKeys: [],
        selectedKeys: [],
        loading: false,
      },
      //片区管理
      areaManage: {
        //所属区域
        area: undefined,
        areaData: [],
        //类型
        type: undefined,
        typeData: [],
        treeData: [],
        expandedKeys: [],
        autoExpandParent: false,
        checkedKeys: [],
        selectedKeys: [],
      },
      //标记管理
      markManage: {
        //所属区域
        area: undefined,
        //类型
        type: undefined,
        typeData: [],
        treeData: [],
        expandedKeys: [],
        autoExpandParent: false,
        checkedKeys: [],
        selectedKeys: [],
      },
      leftMenuVisible: true,
      ProbeRet: {},
      //配置管理
      configPanel: {
        buttonMenuVisible: false,
        buttonMenuIndex: "",
        panelVisible: false,
      },
      conditionQueryInfo: {
        provinceCode: "",
        cityCode: "",
        areaCode: undefined,
        //项目状态
        status: undefined,
      },
      x: 1,
      y: 1,
      z: 1,
      currenPortSource: {},
      showDataSetTree: null,
      cameraTree: null,
      //编辑抽屉弹窗是否可见
      editorDrawerVisible: false,
      gisData: {},
      //视频弹窗是否可见
      videoModalVisible: false,
      //港口规划图弹窗是否可见
      portImgVisible: false,
      //项目详情弹窗弹窗是否可见
      projectDetailVisible: false,
      componentKey: "LiveAction",
      componentVisible: true,
      portLocationShow: false,
      //港区列表
      portLocationSource: [],
      portLocationSourceCopy: [],
      initCamLoc: {
        camPos: [13295950.550773092, 4126494.2874607425, 8415.399365650119],
        camRotate: [
          0.17976041419790642,
          -0.004458807282617025,
          -0.02439236413978944,
          0.9833978468029537,
        ],
        camDir: [0.01753912592413924, 0.3533344868235231, -0.9353326250500272],
      },
      //引擎UI按钮是否可见
      sysUIPanelVisible: false,
      initLoadBimFlag: true,
      //
      portIndex: "areaType08",
      //港区
      portSoucre: [],
      //码头
      wharfSoucre: [],
    };
  },
  beforeCreate() {
    this.simpleImage = Empty.PRESENTED_IMAGE_SIMPLE;
  },
  mounted() {
    this.getData();

    //监听区域管理
    EventBus.$on("regionalUpdate", (data) => {
      this.getAreaManageList();
      this.getAreaTreeList();
      this.getMarkTreeList();
    });

    //监听片区绘制
    EventBus.$on("districtUpdate", (data) => {
      this.getAreaTreeList();
    });

    //监听标记管理
    EventBus.$on("markUpdate", (data) => {
      this.getMarkTreeList();
    });
  },
  methods: {
    //
    handlePortChange(item) {
      let { select, dicItemCode } = item;
      let ports =
        this.bimLayerSource.filter(
          (v) =>
            (this.digitalKeyVal == "DynamicMonitor"
              ? v.markType
              : v.areaType) == dicItemCode
        ) ?? {};
      if (select) {
        if (ports.length == 0) {
          return;
        }
        //显示图层
        if (this.digitalKeyVal == "DynamicMonitor") {
          this.addAnc(ports);
        } else {
          this.addShp(ports);
        }
      } else {
        //影藏图层
        ports.forEach((v) => {
          let { uuid } = v;
          if (this.digitalKeyVal == "DynamicMonitor") {
            BlackHole3D.Anchor.delAnc([`anc_${uuid}`]);
          } else {
            BlackHole3D.Geometry.delShp(`shp_${uuid}`);
          }
        });
      }
    },

    // 选择港区
    handlePort(index) {
      this.portIndex = index;
      let portData = this.bimLayerSource.find((v) => v.areaType == index);
      let { camDir, camPos, camRotate } = portData;
      if (this.digitalKeyVal == "PlanningManage") {
        this.portImgVisible = true;
        this.currenPortSource = portData;
      } else {
        this.setCamLocateTo({
          camDir: JSON.parse(camDir),
          camPos: JSON.parse(camPos),
          camRotate: JSON.parse(camRotate),
        });
      }
    },

    handleSwitch(ev) {
      this.setSysUIPanelVisible(ev);
    },

    showCard(index = 0) {
      this.cardIndex = index;
    },

    getData() {
      //图层
      this.getLayerWorkAreaList();
      this.getLayerProjectList();
      //片区
      this.getAreaManageList();
      this.getAreaTypeList();
      this.getAreaTreeList();
      //标记
      this.getMarkTypeList();
      this.getMarkTreeList();
      //三维场景管理
      this.getThreeTreeList();
    },

    //点击复选框触发
    handleTreeCheck(checkedKeys, e) {
      let { checked, node } = e;
      let { dataRef } = node;
      let flatData = flatTreeData([dataRef], "childs");
      let moduleType = this.getModuleTypeCode();
      //锚点数据(区域和标记都是锚点类型)
      let ancSource = flatData.filter(
        (v) =>
          (v.type == "1" || v.type == "3") &&
          (moduleType == v.moduleType || v.moduleType == "0")
      );
      let ancNames = ancSource.map((v) => `anc_${v.uuid}`);
      //片区数据
      let shpSource = flatData.filter(
        (v) => v.type == "2" && v.moduleType == "2"
      );
      //  (moduleType == v.moduleType || v.moduleType == "0")
      if (!checked) {
        //删除锚点
        BlackHole3D.Anchor.delAnc(ancNames);
        //删除片区
        shpSource.forEach((v) => {
          let { uuid } = v;
          BlackHole3D.Geometry.delShp(`shp_${uuid}`);
        });
      } else {
        //添加相关图层标记
        this.addAnc(ancSource);
        this.addShp(shpSource);
      }
    },

    //点击树节点触发
    handleTreeSelect(checkedKeys, e) {
      let { node } = e;
      try {
        let { camDir, camPos, camRotate } = node.dataRef;
        let camDirVal = JSON.parse(camDir);
        let camPosVal = JSON.parse(camPos);
        let camRotateVal = JSON.parse(camRotate);
        this.setCamLocateToPort({
          camDir: camDirVal,
          camPos: camPosVal,
          camRotate: camRotateVal,
        });
      } catch (error) {}
    },

    //点击复选框触发[图层管理]
    handleLayerTreeCheck(checkedKeys, e) {
      let { checked, node } = e;
      let { dataRef } = node;
      this.initLoadBimFlag = false;
      this.pageSpinning = true;
      this.treeSelectFlag = true;
      let flatData = flatTreeData([dataRef], "subNodes");
      let modalData = flatData.filter(
        (v) =>
          v.modelData && v.modelData.dataSetId && v.modelData.resourcesAddress
      );
      let dataSetIds = modalData.map((v) => v.modelData.dataSetId);
      if (checked) {
        //加载图层
        let dataSetSources = [];
        modalData.forEach((item) => {
          let { modelData } = item;
          let {
            dataSetId,
            resourcesAddress,
            scale,
            rotate,
            translation,
            dataSetCrs,
            dataSetType,
          } = modelData;
          //遥感
          if (dataSetType == 13) {
            this.ygDataSetId = dataSetId;
          }
          dataSetSources.push({
            dataSetId,
            resourcesAddress,
            useTransInfo: true,
            transInfo: [
              scale.split(" ").map((v) => Number(v)),
              rotate.split(" ").map((v) => Number(v)),
              translation.split(" ").map((v) => Number(v)),
            ],
            dataSetCRS: dataSetCrs,
          });
        });
        console.log({ dataSetSources });
        this.loadDataSet(dataSetSources);
      } else {
        //卸载图层
        console.log(dataSetIds);
        this.unloadDataSet(dataSetIds);
      }
    },

    handleLayerTreeSelect(checkedKeys, e) {
      let { node } = e;
      let { dataRef } = node;
      let { modelData, nodeId } = dataRef;
      if (
        modelData?.dataSetId &&
        this.layerManage.checkedKeys.includes(nodeId)
      ) {
        try {
          let { dataSetType, dataSetId } = modelData;
          var backDepth = 2.0;
          var locType = BlackHole3D.RECamDirEm.CAM_DIR_DEFAULT;
          BlackHole3D.Camera.setCamLocateToDataSet(
            dataSetId,
            backDepth,
            locType
          );
        } catch (error) {}
      }
    },

    //点击复选框触发【三维场景】
    handleThreeTreeCheck(checkedKeys, e) {
      let { checked, node } = e;
      let { dataRef } = node;
      this.initLoadBimFlag = false;
      this.pageSpinning = true;
      this.treeSelectFlag = true;
      let flatData = flatTreeData([dataRef], "subNodes");
      let modalData = flatData.filter(
        (v) =>
          v.offsetData && v.modelData.dataSetId && v.modelData.resourcesAddress
      );
      let dataSetIds = modalData.map((v) => v.modelData.dataSetId);
      if (checked) {
        //加载图层
        let dataSetSources = [];
        modalData.forEach((item) => {
          let { modelData, offsetData } = item;
          let {
            dataSetId,
            resourcesAddress,
            dataSetCrs,
            dataSetType,
          } = modelData;
          let { scale, rotate, translation } = offsetData;
          //遥感
          if (dataSetType == 13) {
            this.ygDataSetId = dataSetId;
          }
          dataSetSources.push({
            dataSetId,
            resourcesAddress,
            useTransInfo: true,
            transInfo: [
              scale.split(" ").map((v) => Number(v)),
              rotate.split(" ").map((v) => Number(v)),
              translation.split(" ").map((v) => Number(v)),
            ],
            dataSetCRS: dataSetCrs,
          });
        });
        console.log({ dataSetSources });
        this.loadDataSet(dataSetSources);
      } else {
        //卸载图层
        console.log(dataSetIds);
        this.unloadDataSet(dataSetIds);
      }
    },
    handleThreeTreeSelect(checkedKeys, e) {
      let { node } = e;
      let { dataRef } = node;
      let { modelData, nodeId } = dataRef;
      if (
        modelData?.dataSetId &&
        this.threeManage.checkedKeys.includes(nodeId)
      ) {
        try {
          let { dataSetType, dataSetId } = modelData;
          var backDepth = 2.0;
          var locType = BlackHole3D.RECamDirEm.CAM_DIR_DEFAULT;
          BlackHole3D.Camera.setCamLocateToDataSet(
            dataSetId,
            backDepth,
            locType
          );
        } catch (error) {}
      }
    },

    //加载指定的模型、数据集
    loadDataSet(dataSetList = []) {
      BlackHole3D.Model.loadDataSet(dataSetList, false);
    },

    //卸载指定的模型、数据集
    unloadDataSet(dataSetIds = []) {
      dataSetIds.forEach((v) => {
        v && BlackHole3D.Model.unloadDataSet(v);
      });
    },

    //图层管理区域切换
    layerAreaChange() {
      let { areaData, area = "" } = this.layerManage;
      this.layerManage.checkedKeys = [];
      this.layerManage.treeData = [];
      this.layerManage.proCode = undefined;
      this.layerManage.loading = true;
      switch (area) {
        case "workArea.01":
          this.portIndex = "areaType08";
          break;
        case "workArea.02":
          this.portIndex = "areaType07";
          break;
        case "workArea.03":
          this.portIndex = "areaType09";
          break;
        case "workArea.04":
          this.portIndex = "areaType10";
          break;
        default:
          break;
      }
      Promise.all([
        this.getLayerProjectList(),
        this.getLayerTreeList(),
      ]).finally((_) => {
        this.layerManage.loading = false;
        let flatData = flatTreeData(this.layerManage.treeData, "subNodes");
        let modalData = flatData.filter(
          (v) =>
            v.modelData && v.modelData.dataSetId && v.modelData.resourcesAddress
        );

        let dataSetIds = modalData.map((v) => v.modelData.dataSetId);
        this.layerManage.checkedKeys = flatData.map((v) => v.nodeId);

        //跳转港区
        if (area && area != "quanbu") {
          let current = areaData.find((v) => v.dicItemCode == area);
          current && this.getAreaAngle(current);
        }

        if (area) {
          //加载图层
          let dataSetSources = [];
          modalData.forEach((item) => {
            let { modelData } = item;
            let {
              dataSetId,
              resourcesAddress,
              scale,
              rotate,
              translation,
              dataSetCrs,
              dataSetType,
            } = modelData;
            //遥感
            if (dataSetType == 13) {
              this.ygDataSetId = dataSetId;
            }
            dataSetSources.push({
              dataSetId,
              resourcesAddress,
              useTransInfo: true,
              transInfo: [
                scale.split(" ").map((v) => Number(v)),
                rotate.split(" ").map((v) => Number(v)),
                translation.split(" ").map((v) => Number(v)),
              ],
              dataSetCRS: dataSetCrs,
            });
          });
          this.loadDataSet(dataSetSources);
        } else {
          //卸载图层
          this.unloadDataSet(dataSetIds);
        }
      });
    },

    //查询港区视角
    getAreaAngle(item = {}) {
      let { dicItemName } = item;
      axios
        .post(
          `/probusiness/lygPortAreaRegionMarking/queryDataByNameAndType`,
          {
            name: dicItemName,
            type: 2,
          },
          {
            headers: {
              "Content-Type": "application/json",
            },
          }
        )
        .then((res) => {
          let list = res?.data ?? [];
          let { camDir, camPos, camRotate } = list?.[0] ?? {};
          console.log(camDir);
          console.log(camPos);
          console.log(camRotate);
          this.setCamLocateTo({
            camDir: JSON.parse(camDir),
            camPos: JSON.parse(camPos),
            camRotate: JSON.parse(camRotate),
          });
        })
        .catch((_) => {});
    },

    layerProjectChange() {
      this.layerManage.loading = true;
      this.getLayerTreeList().then((_) => {
        let { proCode, treeData } = this.layerManage;
        let flatData = flatTreeData(treeData, "subNodes");
        let modalData = flatData.filter(
          (v) =>
            v.modelData && v.modelData.dataSetId && v.modelData.resourcesAddress
        );
        let dataSetIds = modalData.map((v) => v.modelData.dataSetId);

        if (proCode) {
          this.layerManage.checkedKeys = flatData.map((v) => v.nodeId);
          //加载图层
          let dataSetSources = [];
          modalData.forEach((item) => {
            let { modelData } = item;
            let {
              dataSetId,
              resourcesAddress,
              scale,
              rotate,
              translation,
              dataSetCrs,
              dataSetType,
            } = modelData;
            //遥感
            if (dataSetType == 13) {
              this.ygDataSetId = dataSetId;
            }
            dataSetSources.push({
              dataSetId,
              resourcesAddress,
              useTransInfo: true,
              transInfo: [
                scale.split(" ").map((v) => Number(v)),
                rotate.split(" ").map((v) => Number(v)),
                translation.split(" ").map((v) => Number(v)),
              ],
              dataSetCRS: dataSetCrs,
            });
          });
          this.loadDataSet(dataSetSources);
        } else {
          this.layerManage.checkedKeys = [];
          //卸载图层
          this.unloadDataSet(dataSetIds);
        }
      });
    },

    //查询图层所属区域
    getLayerWorkAreaList() {
      this.$post("/system/dicSet/getDicItemByCode", {
        code: "workArea",
      })
        .then((res) => {
          let { data } = res;
          this.layerManage.areaData = data ?? [];
          if (this.layerManage.areaData.length > 0) {
            this.layerManage.areaData.unshift({
              dicItemCode: "quanbu",
              dicItemName: "全部",
            });
          }
        })
        .catch((_) => {
          this.layerManage.areaData = [];
        });
    },

    //查询图层管理项目列表
    getLayerProjectList() {
      let { area = "" } = this.layerManage;
      return new Promise((resolve, reject) => {
        axios
          .post(
            `/mdata/sysProject/getProListByAreaAndProCode?workArea=${
              area == "quanbu" ? "" : area
            }&proCode=`,
            {},
            {
              headers: {
                "Content-Type": "application/json",
              },
            }
          )
          .then((res) => {
            this.layerManage.projectData = res?.data ?? [];
            if (this.layerManage.projectData.length > 0) {
              this.layerManage.projectData.unshift({
                proCode: "quanbu",
                proName: "全部",
              });
            }
            resolve();
          })
          .catch((_) => {
            this.layerManage.projectData = [];
            reject();
          });
      });
    },

    //查询地图服务
    getBimMapList() {
      this.pageSpinning = true;
      return new Promise((resolve, reject) => {
        axios
          .post(
            `/probusiness/blackHole3D/project/modelTree/nodeListAllMap`,
            {},
            {
              headers: {
                "Content-Type": "application/json",
              },
            }
          )
          .then((res) => {
            let { data } = res;
            resolve(data);
          })
          .catch((_) => {
            this.pageSpinning = false;
            this.layerManage.treeData = [];
            reject();
          });
      });
    },

    //查询图层管理树
    getLayerTreeList() {
      let { area = "", proCode = "" } = this.layerManage;
      this.layerManage.loading = true;
      //   this.pageSpinning = true;
      return new Promise((resolve, reject) => {
        axios
          .post(
            `/probusiness/blackHole3D/project/modelTree/nodeListAllModel`,
            {
              workArea: area == "quanbu" ? "" : area,
              proCode: proCode == "quanbu" ? "" : proCode,
            },
            {
              headers: {
                "Content-Type": "application/json",
              },
            }
          )
          .then((res) => {
            let { data } = res;
            let filterData = addAttributeByKey(
              null,
              "scopedSlots",
              { icon: "custom" },
              data ?? [],
              "subNodes"
            );
            this.layerManage.treeData = filterData;
            let keys = flatTreeData(
              filterData.filter((v) => v.nodeId),
              "subNodes"
            ).map((v) => v.nodeId);
            this.layerManage.checkedKeys = keys;
            resolve(data);
          })
          .catch((_) => {
            this.pageSpinning = false;
            this.layerManage.treeData = [];
            reject();
          })
          .finally((_) => {
            this.layerManage.loading = false;
          });
      });
    },

    //查询三维场景树
    getThreeTreeList() {
      this.threeManage.loading = true;
      return new Promise((resolve, reject) => {
        axios
          .post(
            `/probusiness/blackHole3D/project/modelTree/nodeListAllDem`,
            {},
            {
              headers: {
                "Content-Type": "application/json",
              },
            }
          )
          .then((res) => {
            let { data } = res;
            let filterData = addAttributeByKey(
              null,
              "scopedSlots",
              { icon: "custom" },
              data ?? [],
              "subNodes"
            );
            this.threeManage.treeData = filterData;
            let keys = flatTreeData(
              filterData.filter((v) => v.nodeId),
              "subNodes"
            ).map((v) => v.nodeId);
            this.threeManage.checkedKeys = keys;

            //加载图层
            // let flatData = flatTreeData(this.threeManage.treeData, "subNodes");
            // let modalData = flatData.filter(
            //   (v) =>
            //     v.modelData &&
            //     v.modelData.dataSetId &&
            //     v.modelData.resourcesAddress
            // );
            // let dataSetSources = [];
            // modalData.forEach((item) => {
            //   let { modelData } = item;
            //   let {
            //     dataSetId,
            //     resourcesAddress,
            //     scale,
            //     rotate,
            //     translation,
            //     dataSetCrs,
            //   } = modelData;
            //   dataSetSources.push({
            //     dataSetId,
            //     resourcesAddress,
            //     useTransInfo: true,
            //     transInfo: [
            //       scale.split(" ").map((v) => Number(v)),
            //       rotate.split(" ").map((v) => Number(v)),
            //       translation.split(" ").map((v) => Number(v)),
            //     ],
            //     dataSetCRS: dataSetCrs,
            //   });
            // });
            // this.loadDataSet(dataSetSources);
            resolve(data);
          })
          .catch((_) => {
            this.threeManage.checkedKeys = [];
            this.threeManage.treeData = [];
            reject();
          })
          .finally((_) => {
            this.threeManage.loading = false;
          });
      });
    },

    //查询片区区域选择框
    getAreaManageList() {
      axios
        .post(
          `/probusiness/lygPortAreaRegionMarking/queryRegionTree`,
          {
            moduleType: this.getModuleTypeCode(),
          },
          {
            headers: {
              "Content-Type": "application/json",
            },
          }
        )
        .then((res) => {
          let filterData = addAttributeByKey(
            null,
            "scopedSlots",
            { icon: "custom" },
            res?.data ?? [],
            "childs"
          );
          this.areaManage.areaData = filterData;
        })
        .catch((_) => {
          this.areaManage.areaData = [];
        });
    },

    //查询片区类型
    getAreaTypeList() {
      this.$post("/system/dicSet/getDicItemByCode", {
        code: "areaType",
      })
        .then((res) => {
          let { data } = res;
          this.areaManage.typeData = data ?? [];
          let codes = ["areaType07", "areaType08", "areaType09", "areaType10"];
          this.portSoucre = this.areaManage.typeData.filter((v) =>
            codes.includes(v.dicItemCode)
          );
          this.wharfSoucre = this.areaManage.typeData.filter(
            (v) => !codes.includes(v.dicItemCode)
          );
          this.portSoucre.forEach((v) => {
            this.$set(v, "select", true);
          });
          this.wharfSoucre.forEach((v) => {
            this.$set(v, "select", true);
          });
        })
        .catch((_) => {
          this.areaManage.typeData = [];
          this.portSoucre = [];
          this.wharfSoucre = [];
        });
    },

    //查询片区管理树
    getAreaTreeList() {
      let { area = "", type = "" } = this.areaManage;
      return new Promise((resolve, reject) => {
        axios
          .post(
            `/probusiness/lygPortAreaRegionMarking/queryAreaList`,
            {
              moduleType: this.getModuleTypeCode(),
              region: area,
              areaType: type,
            },
            {
              headers: {
                "Content-Type": "application/json",
              },
            }
          )
          .then((res) => {
            let { data } = res;
            let filterData = addAttributeByKey(
              null,
              "scopedSlots",
              { icon: "custom" },
              data,
              "childs"
            );
            this.areaManage.treeData = filterData;
            let keys = flatTreeData(filterData, "childs").map((v) => v.uuid);
            this.areaManage.checkedKeys = keys;
            resolve();
          })
          .catch((_) => {
            this.areaManage.treeData = [];
            reject();
          });
      });
    },

    //查询标记管理类型
    getMarkTypeList() {
      this.$post("/system/dicSet/getDicItemByCode", {
        code: "markManagerType",
      })
        .then((res) => {
          let { data } = res;
          this.markManage.typeData = data ?? [];
          this.markManage.typeData.forEach((v) => {
            this.$set(v, "select", true);
          });
        })
        .catch((_) => {
          this.markManage.typeData = [];
        });
    },

    //查询标记管理树
    getMarkTreeList() {
      let { area = "", type = "" } = this.markManage;
      return new Promise((resolve, reject) => {
        axios
          .post(
            `/probusiness/lygPortAreaRegionMarking/queryMarkingList`,
            {
              moduleType: this.getModuleTypeCode(),
              region: area,
              markType: type,
            },
            {
              headers: {
                "Content-Type": "application/json",
              },
            }
          )
          .then((res) => {
            let { data } = res;
            let filterData = addAttributeByKey(
              null,
              "scopedSlots",
              { icon: "custom" },
              data,
              "childs"
            );
            this.markManage.treeData = filterData;
            let keys = flatTreeData(filterData, "childs").map((v) => v.uuid);
            this.markManage.checkedKeys = keys;
            resolve();
          })
          .catch((_) => {
            this.markManage.treeData = [];
            reject();
          });
      });
    },

    onExpand(expandedKeys, keyName) {
      this[keyName].expandedKeys = expandedKeys;
      this[keyName].autoExpandParent = false;
    },

    openLeftMenu() {
      this.leftMenuVisible = !this.leftMenuVisible;
    },

    handleConfigBtnMouseEnter() {
      this.configPanel.buttonMenuVisible = false;
    },

    handleConfigMouseLeave() {
      this.configPanel.buttonMenuVisible = true;
    },

    //打开配置面板
    openConfigPanel(type = 0) {
      this.sysUIPanelVisible = false;
      BlackHole3D.Graphics.setSysUIPanelVisible(false);
      this.configPanel.buttonMenuIndex = type;
      this.configPanel.panelVisible = true;
      this.configPanel.buttonMenuVisible = true;
    },

    //关闭
    closeConfigPanel() {
      this.configPanel.panelVisible = false;
      this.configPanel.buttonMenuVisible = false;
      setTimeout((_) => {
        this.configPanel.buttonMenuIndex = "";
      }, 100);
    },

    //
    checkListPannel(type = null) {
      this.cameraTree = type;
      this.showDataSetTree = type;
      this.conditionQueryInfo = {
        provinceCode: "",
        cityCode: "",
        areaCode: undefined,
        //项目状态
        status: undefined,
      };
    },

    //查询港区列表
    getPortListBaseSource() {
      this.$post("/probusiness/lygPortArea/getList")
        .then((res) => {
          let { data } = res;
          data.forEach((v) => {
            let { portCoordinates, portView } = v;
            v.portCoordinates = JSON.parse(portCoordinates || "[]");
            // //绘制实景电子围栏
            // if (portView && portView.trim()) {
            //   let portViewList = JSON.parse(portView || "[]");
            //   portViewList.forEach((port) => {
            //     this.AddPlane(port, "portView");
            //   });
            // }
          });
          //   this.portLocationSourceCopy = cloneDeep(data ?? []);
          this.portLocationSource = data ?? [];
          //添加港区位置marker
          this.addPortLocationMarker();
          //
        })
        .catch((_) => {
          this.portLocationSource = [];
          //   this.portLocationSourceCopy = [];
        });
    },

    //查询所有bim覆盖物列表
    getBimLayerSource(type) {
      if (type == "handleActive") {
        try {
          //清空所有片区
          BlackHole3D.Geometry.delAllShps();
          //清空所有锚点
          BlackHole3D.Anchor.delAllAnc();
        } catch (error) {}
      }

      return new Promise((resolve, reject) => {
        axios
          .post(
            `/probusiness/lygPortAreaRegionMarking/queryList`,
            {
              moduleType: "",
              type: "",
            },
            {
              headers: {
                "Content-Type": "application/json",
              },
            }
          )
          .then((res) => {
            let { statusCode, data } = res;
            this.bimLayerSource = data ?? [];
            let moduleType = this.getModuleTypeCode();
            if (statusCode == 200) {
              //锚点数据(区域和标记都是锚点类型)
              let ancSource = data.filter(
                (v) =>
                  (v.type == "1" || v.type == "3") &&
                  (moduleType == v.moduleType ||
                    v.moduleType == "0" ||
                    this.extra == "EngineeringManage")
              );
              //片区数据
              let shpSource = data.filter(
                (v) => v.type == "2" && v.moduleType == "2"
              );
              //(moduleType == v.moduleType || v.moduleType == "0")
              //开始绘制相关覆盖物
              setTimeout((_) => {
                this.addAnc(ancSource);
                if (moduleType == "2") {
                  this.addShp(shpSource);
                }
              });
              resolve();
            }
          })
          .catch((_) => {
            reject();
          })
          .finally((_) => {});
      });
    },

    getModuleTypeCode() {
      switch (this.digitalKey()) {
        //港区实景
        case "LiveAction":
          return "1";

        //规划管理
        case "PlanningManage":
          return "2";

        //项目千里眼
        case "DynamicMonitor":
          return "3";

        default:
          break;
      }
    },

    //监听港区mmarker点击
    portLocationClick(port = {}) {
      let { camDir, camPos, camRotate } = port;
      let key = this.digitalKey();
      this.currenPortSource = port;
      switch (key) {
        //港区实景
        case "LiveAction":
          this.setCamLocateToPort({
            camDir: JSON.parse(camDir || "[]"),
            camPos: JSON.parse(camPos || "[]"),
            camRotate: JSON.parse(camRotate || "[]"),
          });
          break;

        //港区管理
        case "PlanningManage":
          this.portImgVisible = true;
          break;

        //动态监测
        case "DynamicMonitor":
          this.setCamLocateToPort({
            camDir: JSON.parse(camDir || "[]"),
            camPos: JSON.parse(camPos || "[]"),
            camRotate: JSON.parse(camRotate || "[]"),
          });
          break;

        default:
          break;
      }
    },

    //设置相机方位进入港区
    setCamLocateToPort(data = {}) {
      try {
        let camLoc = new BlackHole3D.RECamLoc();
        let { camDir, camPos, camRotate } = data;
        camLoc.camDir = camDir;
        camLoc.camPos = camPos;
        camLoc.camRotate = camRotate;
        BlackHole3D.Camera.setCamLocateTo(camLoc, 0.5, 1);
      } catch (error) {}
    },

    //添加锚点
    addAnc(dataSource = []) {
      var ancList = [];
      let groupName = `${this.digitalKey()}_anc`;
      dataSource.forEach((v) => {
        let {
          portCoordinates,
          uuid,
          icon,
          name,
          iconWidth,
          iconHeight,
          textColor,
          textBorderColor,
        } = v;
        let tColor = this.hexToRgba(textColor);
        let bColor = this.hexToRgba(textBorderColor);
        ancList.push({
          groupName: groupName,
          ancName: `anc_${uuid}`,
          pos: JSON.parse(portCoordinates),
          picPath: icon,
          textInfo: name,
          picWidth: Number(iconWidth),
          picHeight: Number(iconHeight),
          linePos: [0, 0],
          lineClr: new BlackHole3D.REColor(255, 0, 0, 255),
          ancSize: 60,
          selfAutoScaleDist: -1,
          selfVisDist: -1,
          //字体位置
          texBias: [0, 1],
          //字体颜色
          textClr: new BlackHole3D.REColor(
            tColor?.[0] ?? 255,
            tColor?.[1] ?? 255,
            tColor?.[2] ?? 255,
            255
          ),
          //文字描边
          textBorderClr: new BlackHole3D.REColor(
            bColor?.[0] ?? 255,
            bColor?.[1] ?? 255,
            bColor?.[2] ?? 255,
            255
          ),
          texFocus: [Math.ceil(iconWidth / 2), 0],
        });
      });
      BlackHole3D.Anchor.addAnc(ancList);
      //设置系统中锚点不允许被场景遮挡
      BlackHole3D.Anchor.setAncCanOverlap(groupName, false);
    },

    //绘制片区
    addShp(dataSource = []) {
      dataSource.forEach((v) => {
        let {
          areaColorBackground,
          areaColorBorderWidth,
          areaColorFill,
          areaColorBorderColor,
          areaColorFrame,
          areaColorWriting,
          uuid,
          portCoordinates,
          name,
        } = v;
        let pathList = JSON.parse(portCoordinates ?? "[]");
        if (pathList.length < 3) {
          return;
        }
        let shpName = `shp_${uuid}`;
        //边框颜色
        let bColor = this.hexToRgba(areaColorFrame);
        //区域填充色
        let fColor = this.hexToRgba(areaColorFill);
        //文字颜色
        let tColor = this.hexToRgba(areaColorWriting);
        //文字描边
        let textBColor = this.hexToRgba(areaColorBorderColor);
        //矢量文字信息
        var shpTextInfo = new BlackHole3D.REShpTextInfo();
        shpTextInfo.text = name;
        shpTextInfo.texBias = [0, 0];
        shpTextInfo.fontName = "RealBIMFont001";
        shpTextInfo.textClr = new BlackHole3D.REColor(
          tColor?.[0] ?? 255,
          tColor?.[1] ?? 255,
          tColor?.[2] ?? 255,
          255
        );
        shpTextInfo.textBorderClr = new BlackHole3D.REColor(
          textBColor?.[0] ?? 255,
          textBColor?.[1] ?? 255,
          textBColor?.[2] ?? 255,
          255
        );
        //矢量线信息
        var lineShpInfo = new BlackHole3D.RELineShpInfo();
        lineShpInfo.shpName = shpName;
        lineShpInfo.potList = pathList;
        lineShpInfo.fillState = 1;
        //边框颜色
        lineShpInfo.lineClr = new BlackHole3D.REColor(
          bColor?.[0] ?? 255,
          bColor?.[1] ?? 255,
          bColor?.[2] ?? 255,
          255
        );
        //填充色
        lineShpInfo.fillClr = new BlackHole3D.REColor(
          fColor?.[0] ?? 255,
          fColor?.[1] ?? 255,
          fColor?.[2] ?? 255,
          255 *
            (Math.abs(areaColorBackground) > 1
              ? 1
              : Math.abs(areaColorBackground))
        );
        lineShpInfo.textPos = -3;
        lineShpInfo.scrASDist = -1.0;
        lineShpInfo.scrVisDist = -1;
        lineShpInfo.contactSce = false;
        lineShpInfo.lineWidth = Number(areaColorBorderWidth) || 2;
        lineShpInfo.textInfo = shpTextInfo;
        let Geometry = BlackHole3D.Geometry.addPolylineShp(lineShpInfo);
        if (!Geometry) {
          this.$message.error("片区绘制失败，请稍后重试！");
        }
      });
    },

    // 获取图片尺寸
    getImageSize(src) {
      return new Promise((resolve, reject) => {
        const img = new Image();
        img.onload = function() {
          const width = img.width;
          const height = img.height;
          resolve({ width, height });
        };
        img.onerror = function() {
          reject(new Error("无法加载图片"));
        };
        img.src = src;
      });
    },

    //绘制面
    AddPlane(data = {}, type = "") {
      let {
        posList,
        uuid,
        borderColor,
        fillColor,
        opacity,
        name,
        textColor,
      } = data;
      let bColor = this.hexToRgba(borderColor);
      let fColor = this.hexToRgba(fillColor);
      let tColor = this.hexToRgba(textColor);
      let posListArr = posList.map((v) => JSON.parse(v));
      //矢量文字信息
      var shpTextInfo = new BlackHole3D.REShpTextInfo();
      shpTextInfo.text = name;
      shpTextInfo.texBias = [0, 0];
      shpTextInfo.fontName = `RealBIMFont001`;
      shpTextInfo.textClr = new BlackHole3D.REColor(
        tColor[0],
        tColor[1],
        tColor[2],
        255
      );
      shpTextInfo.textBorderClr = new BlackHole3D.REColor(0, 0, 0, 255);
      shpTextInfo.textBackMode = 0;
      shpTextInfo.textBackBorder = 0;
      shpTextInfo.textBackClr = new BlackHole3D.REColor(0, 0, 0, 0);
      //矢量线信息
      var lineShpInfo = new BlackHole3D.RELineShpInfo();
      lineShpInfo.shpName = `plane_${uuid}`;
      lineShpInfo.potList = posListArr;
      lineShpInfo.fillState = 1;
      lineShpInfo.lineClr = new BlackHole3D.REColor(
        bColor[0],
        bColor[1],
        bColor[2],
        255
      );
      lineShpInfo.fillClr = new BlackHole3D.REColor(
        fColor[0],
        fColor[1],
        fColor[2],
        opacity ? Math.abs(opacity) * 255 : 255
      );
      lineShpInfo.textPos = -2;
      lineShpInfo.scrASDist = -1.0;
      lineShpInfo.scrVisDist = 12800;
      lineShpInfo.contactSce = false;
      lineShpInfo.lineWidth = 2;
      lineShpInfo.textInfo = shpTextInfo;
      lineShpInfo.groupName = `${type}`;
      var addlineShpBool = new BlackHole3D.Geometry.addPolylineShp(lineShpInfo);
    },

    //16进制颜色转rgb颜色
    hexToRgba(hex, opacity) {
      if (!hex) hex = "#ededed";
      let r = parseInt("0x" + hex.slice(1, 3));
      let g = parseInt("0x" + hex.slice(3, 5));
      let b = parseInt("0x" + hex.slice(5, 7));
      let rgba = "rgba(" + r + "," + g + "," + b + "," + (opacity ?? "1") + ")";
      return [r, g, b];
    },

    //系统引擎创建完成回调【加载模型资源】
    onEngineCreated() {
      let dom = this.$refs.blackHoleContainer;
      let BlackHole3D = window.BlackHole3D;
      canvasHolder.moveCanvasToTarget(this.$refs.blackHoleContainer);
      BlackHole3D.m_re_em_window_width = dom.clientWidth;
      BlackHole3D.m_re_em_window_height = dom.clientHeight;
      BlackHole3D.Coordinate.setEngineWorldCRS("EPSG:3857");
      //
      this.getBimMapList().then((res) => {
        let modalData = res;
        //开始加载一个或多个模型资源
        let dataSetSources = [];
        modalData.forEach((item) => {
          let { modelData } = item;
          let {
            dataSetId,
            resourcesAddress,
            scale,
            rotate,
            translation,
            dataSetCrs,
          } = modelData;
          dataSetSources.push({
            dataSetId,
            resourcesAddress,
            useTransInfo: true,
            transInfo: [
              scale.split(" ").map((v) => Number(v)),
              rotate.split(" ").map((v) => Number(v)),
              translation.split(" ").map((v) => Number(v)),
            ],
            dataSetCRS: dataSetCrs,
          });
        });
        //开始加载一个或多个模型资源
        BlackHole3D.Model.loadDataSet(dataSetSources);
        //设置渲染时引擎最大限制的显存占用空间(以MB为单位)
        BlackHole3D.Common.setMaxResMemMB(3000);
        //设置渲染时引擎期望分配的显存空间(以MB为单位)
        BlackHole3D.Common.setExpectMaxInstMemMB(2500);
        //设置模型每帧最大渲染面数
        BlackHole3D.Common.setExpectMaxInstDrawFaceNum(10000000);
        //设置页面调度等级，等级越高，模型加载越快，对硬件要求越高
        BlackHole3D.Common.setPageLoadLev(2);
      });
      //查询模型列表
      this.getLayerTreeList().then((res) => {});
    },

    //监听窗口尺寸变化
    onResize() {
      let box = this.$refs["blackHoleContainer"];
      if (box) {
        window.BlackHole3D.m_re_em_window_width = window.innerWidth;
        window.BlackHole3D.m_re_em_window_height = window.innerHeight;
      }
    },

    addEventListener() {
      //场景模型加载完成回调
      document.addEventListener(
        "REDataSetLoadFinish",
        this.dataSetLoadFinishCallBack
      );

      window.addEventListener("resize", this.onResize);

      //鼠标探测矢量元素事件
      document.addEventListener(
        "RESystemSelShpElement",
        this.RESystemSelShpElement
      );
      //鼠标探测模型事件
      document.addEventListener("RESystemSelElement", this.constructClick);

      //
      document.addEventListener("RESystemUIEvent", (e) => {
        this.bimToolBarShow =
          BlackHole3D.Graphics.getBtnActiveState("BuiltIn_Btn_Measure") == 0;
      });
    },

    dataSetLoadFinishCallBack() {
      //设置模型偏移量
      setTimeout((_) => {
        this.setAllDataSetTransform();
      }, 2000);
      //设置系统UI
      this.setSystemUI();
      //调整遥感图偏移量
      // this.setDataSetTransform();
      //设置相机方位
      this.initLoadBimFlag && !this.treeSelectFlag && this.setCamLocateTo();
      //查询港区列表
      this.getPortListBaseSource();
      //查询所有bim覆盖物列表
      this.initLoadBimFlag && this.getBimLayerSource();
      this.pageSpinning = false;
      this.initLoadBimFlag = false;
    },

    //设置模型偏移量
    setAllDataSetTransform() {
      let allIds = BlackHole3D.Model.getAllDataSetId();
      let flatData = flatTreeData(this.layerManage.treeData, "subNodes");
      flatData.forEach((v) => {
        let { modelData, offsetData } = v;
        if (modelData && offsetData) {
          let { dataSetId, rotate, scale, translation } = offsetData;
          if (allIds.includes(dataSetId)) {
            try {
              var locInfo = new BlackHole3D.RELocInfo();
              locInfo.scale = scale.split(" ").map((v) => Number(v));
              locInfo.rotate = rotate.split(" ").map((v) => Number(v));
              locInfo.offset = translation.split(" ").map((v) => Number(v));
              BlackHole3D.Coordinate.setDataSetTransform(dataSetId, locInfo);
            } catch (error) {}
          }
        }
      });
    },

    //鼠标探测矢量元素事件 【锚点】
    async RESystemSelShpElement() {
      var ProbeRet = BlackHole3D.Probe.getCurShpProbeRet();
      this.ProbeRet = ProbeRet;
      let { elemId } = ProbeRet;
      console.log("锚点==", { ProbeRet });
      if (!elemId) {
        return;
      }
      let { bimLayerSource } = this;
      if (elemId.startsWith("anc_")) {
        //
        let uuid = elemId.split("anc_")?.[1] ?? "";
        if (uuid) {
          let data = bimLayerSource.find((v) => v.uuid == uuid);
          let { markType, camDir, camPos, camRotate, parentId } = data;
          this.ancUUID = data.markForeignCode;
          //
          if (!parentId && this.digitalKeyVal == "PlanningManage") {
            //港区规划
            this.portImgVisible = true;
            this.currenPortSource = data;
          } else {
            this.setCamLocateToPort({
              camDir: JSON.parse(camDir || "[]"),
              camPos: JSON.parse(camPos || "[]"),
              camRotate: JSON.parse(camRotate || "[]"),
            });
          }

          //
          switch (markType) {
            //视频监控锚点
            case "markManagerType01":
              this.videoModalVisible = true;
              this.projectDetailVisible = false;
              break;

            //项目锚点
            case "markManagerType02":
              this.projectDetailVisible = true;
              this.videoModalVisible = false;
              break;

            default:
              break;
          }
          console.log(uuid, data);
        }
      }
    },

    getPortData(uuid = "") {
      return new Promise((resolve, reject) => {
        if (!uuid) {
          resolve([]);
          return;
        }
        this.portLocationSource.forEach((v) => {
          let { equipment } = v;
          let listEqu = JSON.parse(equipment || "[]");
          if (listEqu.find((item) => item.uuid == uuid)) {
            resolve(listEqu);
          }
        });
      });
    },

    //调整遥感图偏移量
    setDataSetTransform() {
      if (!this.ygDataSetId) {
        return;
      }
      let scale = [1, 1, 1];
      let rotate = [0, 0, 0, 0];
      let offset = [0, 0, 300];
      var locInfo = new BlackHole3D.RELocInfo();
      locInfo.scale = scale;
      locInfo.rotate = rotate;
      locInfo.offset = offset;
      BlackHole3D.Coordinate.setDataSetTransform(this.ygDataSetId, locInfo);
    },

    //监听构件点击时间
    constructClick(e) {
      let { detail } = e;
      let { editorDrawerVisible } = this;
      if (detail.button == 0) {
        //左键单击
        var ProbeRet = BlackHole3D.Probe.getCurProbeRet();
        this.ProbeRet = ProbeRet;
        console.log("ProbeRet", ProbeRet);
        let { dataSetId, elemId } = ProbeRet;
        //处于编辑状态
        if (editorDrawerVisible) {
          let { district, zone } = this.$refs["customEditorDrawer"].form;
          if (district) {
            console.log(ProbeRet);
            this.gisData = ProbeRet;
            if (zone == 1) {
              this.updatePortLocationMarker(district, ProbeRet.elemPos);
            }
          }
        }
      } else {
        //右键单击
        console.log(e);
      }
    },

    //更新港区位置marker
    updatePortLocationMarker(uuid, pos) {
      this.portLocationSource.forEach((v, i) => {
        if (v.uuid == uuid) {
          var [x, y] = BlackHole3D.Coordinate.getWorldPosToScreenPos(
            pos ?? [],
            100
          );
          this.$set(v, "portCoordinates", pos);
          this.$set(v, "position", { left: x, bottom: y });
          this.$set(v, "icon", `location_icon_${i + 1}`);
        }
      });
    },

    //添加港区位置marker
    addPortLocationMarker() {
      this.portLocationShow = true;
      document.addEventListener("RECameraMove", (e) => this.RECameraMove(e));
      this.RECameraMove();
    },

    //监听相机移动
    RECameraMove(e) {
      this.portLocationSource.forEach((v, i) => {
        let { portCoordinates } = v;
        var [x, y] = BlackHole3D.Coordinate.getWorldPosToScreenPos(
          portCoordinates ?? [],
          100
        );
        this.$set(v, "position", { left: x, bottom: y });
        this.$set(v, "icon", `location_icon_${i + 1}`);
      });
      return this.portLocationSource;
    },

    //设置相机方位
    setCamLocateTo(data) {
      let camLoc = new BlackHole3D.RECamLoc();
      let { camDir, camPos, camRotate } = data || this.initCamLoc;
      camLoc.camDir = camDir;
      camLoc.camPos = camPos;
      camLoc.camRotate = camRotate;
      BlackHole3D.Camera.setCamLocateTo(camLoc, 0.5, 1);
    },

    //设置系统UI
    setSystemUI() {
      BlackHole3D.Graphics.setGeoCoordVisible(false);
      BlackHole3D.Graphics.setViewCubeVisible(false);
      BlackHole3D.Graphics.setSysUIPanelVisible(false);
      BlackHole3D.Graphics.setSysUIColorStyle(false);
      BlackHole3D.Graphics.setSysPanelUIDockArea(3);
    },

    //设置引擎UI按钮是否可见
    setSysUIPanelVisible(visible = false) {
      BlackHole3D.Graphics.setSysUIPanelVisible(visible);
      setTimeout((_) => {
        this.sysUIPanelVisible = visible;
      }, 0);
    },

    setAngleView() {
      let portData = this.bimLayerSource.find(
        (v) => v.areaType == this.portIndex
      );
      let { camDir, camPos, camRotate } = portData;
      this.setCamLocateTo({
        camDir: JSON.parse(camDir),
        camPos: JSON.parse(camPos),
        camRotate: JSON.parse(camRotate),
      });
    },

    //模块切换
    handleActive(key) {
      switch (key) {
        case "LiveAction":
          this.areaManage.area = undefined;
          this.areaManage.type = undefined;
          this.markManage.area = undefined;
          this.markManage.type = undefined;
          break;
        case "PlanningManage":
          this.layerManage.area = undefined;
          this.layerManage.proCode = undefined;
          this.markManage.area = undefined;
          this.markManage.type = undefined;
          break;
        case "DynamicMonitor":
          this.layerManage.area = undefined;
          this.layerManage.proCode = undefined;
          this.areaManage.area = undefined;
          this.areaManage.type = undefined;
          break;
        default:
          break;
      }
      this.videoModalVisible = false;
      this.projectDetailVisible = false;
      //   this.setCamLocateTo();
      if (this.buttonKey == key) {
        this.componentVisible = true;
        return;
      }
      this.getAreaManageList();
      this.getAreaTreeList();
      this.getMarkTreeList();
      this.getBimLayerSource("handleActive");
      this.buttonKey = key;
      this.componentVisible = false;
      setTimeout((_) => {
        this.componentKey = key;
        this.componentVisible = true;
        this.setAngleView();
      }, 300);
    },

    //获取相机方位
    getCamLocate() {
      console.log(BlackHole3D.Camera.getCamLocate());
    },

    //绘制电子围栏
    addFenceByPot() {
      this.projectDetailVisible = false;
    },
    //监听项目定位
    changeProPosition() {
      let camDir =
        "[-0.14850754798803745, 0.5586994552828733, -0.8159659471186291]";
      let camPos = "[13295280.341918506, 4124615.613779721, 7970.761433750959]";
      let camRotate =
        "[0.3007873373132639, 0.03929381825023122, 0.12343234701513542, 0.944853125765931]";
      this.setCamLocateToPort({
        camDir: JSON.parse(camDir || "[]"),
        camPos: JSON.parse(camPos || "[]"),
        camRotate: JSON.parse(camRotate || "[]"),
      });
    },

    removeEventListener() {
      document.removeEventListener(
        "REDataSetLoadFinish",
        this.dataSetLoadFinishCallBack
      );
      window.removeEventListener("resize", this.onResize);
      document.removeEventListener(
        "RESystemSelShpElement",
        this.RESystemSelShpElement
      );
      document.removeEventListener("RESystemSelElement", this.constructClick);
      document.removeEventListener("RECameraMove", () => {});
    },
  },
  beforeDestroy() {
    this.removeEventListener();
    releaseEngine();
  },
};
</script>
<style lang="less" scoped>
.gis-container {
  position: absolute;
  width: 100%;
  height: 100%;
  top: 0;
  left: 0;
  transition: 0.3s;
  .page-spinning {
    position: absolute;
    top: 50%;
    left: 50%;
    transform: translate(-50%, -50%);
  }
  //
  .left-menu-container {
    position: absolute;
    width: 260px;
    height: 100%;
    top: 0;
    left: 20px;
    z-index: 9;
    box-sizing: border-box;
    padding: 110px 0 90px 0;
    transition: 0.3s;
    &.hide {
      left: -370px;
    }
    .body {
      height: 100%;
      position: relative;
      .body-container {
        height: 100%;
        display: flex;
        flex-direction: column;
        position: relative;
        .card-container {
          flex: 1;
          flex-shrink: 0;
          display: flex;
          flex-direction: column;
          overflow: hidden;
          transition: 0.3s;
          &.hide {
            height: 42px;
            flex: none;
            overflow: hidden;
            .card-header {
              .button {
                opacity: 0.6;
                background: url("~@/assets/img/portalEntry/icon_16.png");
                background-size: 100% 100%;
              }
            }
          }
          &:nth-child(2),
          &:nth-child(3),
          &:nth-child(4) {
            margin-top: 12px;
          }
          .card-header {
            height: 40px;
            flex-shrink: 0;
            background: url("~@/assets/img/portalEntry/icon_6.png");
            background-size: 100% 100%;
            display: flex;
            align-items: center;
            box-sizing: border-box;
            color: #eefaff;
            font-family: Microsoft YaHei;
            font-size: 16px;
            padding-left: 46px;
            position: relative;
            .button {
              position: absolute;
              width: 20px;
              height: 20px;
              cursor: pointer;
              top: 15px;
              right: 15px;
              background: url("~@/assets/img/portalEntry/icon_13.png");
              background-size: 100% 100%;
              opacity: 1;
            }
          }
          .card-content {
            flex: 1;
            border-radius: 0px 0px 0px 8px;
            border: 1px solid rgba(0, 213, 255, 0.4);
            background: rgba(5, 62, 74, 0.7);
            display: flex;
            flex-direction: column;
            overflow: hidden;
            .condition {
              flex-shrink: 0;
              padding: 16px 10px 6px 10px;
              /deep/.ant-select {
                width: 100%;
                &:last-child {
                  //   margin-left: 10px;
                }
                .ant-select-selection {
                  background-color: rgba(0, 213, 255, 0.1);
                  border-color: #00d5ff;
                  color: #eef9ff;
                }
                .ant-select-selection__clear {
                  background: none;
                }
                //清空按钮
                .anticon-close-circle {
                  color: #eef9ff;
                }
                //箭头图标
                .anticon-down {
                  color: #eef9ff;
                }
              }
            }
            .tree-container {
              flex: 1;
              padding: 0 10px;
              color: #e0f8ff;
              position: relative;
              overflow-y: auto;
              overflow-x: hidden;
              .card-spinning {
                position: absolute;
                top: 50%;
                left: 50%;
                transform: translate(-50%, -50%);
              }
              /deep/.ant-empty {
                opacity: 0.6;
                .ant-empty-description {
                  color: #eef9ff;
                }
              }

              /deep/.ant-tree {
                .ant-tree-switcher {
                  .anticon {
                    font-size: 16px !important;
                    color: #e0f8ff;
                  }
                }
                .ant-tree-checkbox {
                  .ant-tree-checkbox-inner {
                    background: rgba(0, 144, 255, 0.2);
                    border: 1px solid #0090ff;
                    border-radius: 2px;
                  }
                  &.ant-tree-checkbox-checked {
                    .ant-tree-checkbox-inner {
                      background: #26ffab;
                      border: 1px solid #26ffab;
                      &::after {
                        border-color: #00316c;
                      }
                    }
                  }
                  &.ant-tree-checkbox-indeterminate {
                    .ant-tree-checkbox-inner {
                      border: 1px solid #26ffab;
                      &:after {
                        background: #26ffab;
                      }
                    }
                  }
                }
                .ant-tree-node-content-wrapper {
                  width: calc(100% - 34px);
                  &:hover,
                  &.ant-tree-node-selected {
                    background-color: rgba(0, 144, 255, 0.8) !important;
                  }
                  .ant-tree-title {
                    width: calc(100% - 24px);
                    display: inline-block;
                    color: #eef9ff;
                    font-size: 16px;
                    overflow: hidden;
                    text-overflow: ellipsis;
                    white-space: nowrap;
                  }
                }
              }
            }
          }
        }
      }
      .open-button {
        position: absolute;
        width: 36px;
        height: 32px;
        background: url("~@/assets/img/portalEntry/icon_14.png");
        background-size: 100% 100%;
        top: 9px;
        right: -52px;
        cursor: pointer;
        transition: 0.3s;
        &.hide {
          background: url("~@/assets/img/portalEntry/icon_15.png");
          background-size: 100% 100%;
          right: -180px;
        }
      }
    }
  }
  //
  .bim-container {
    width: 100%;
    height: 100%;
  }
  //自定义滚动条
  .custom-scrollbar {
    overflow: auto !important;
    overflow-x: overlay !important;
    overflow-y: overlay !important;
    //滚动条整体样式
    &::-webkit-scrollbar {
      width: 6px;
      height: 10px;
    }

    //滚动条里面小方块
    &::-webkit-scrollbar-thumb {
      border-radius: 10px;
      background: rgba(0, 144, 255, 0.6);
    }

    //滚动条里面轨道
    &::-webkit-scrollbar-track {
      border-radius: 10px;
      background: rgba(0, 144, 255, 0.1);
    }
    //边角，即两个滚动条的交汇处
    &::-webkit-scrollbar-corner {
      background: none;
    }
  }
  &.hide {
    opacity: 0;
  }
  .BlackHole-container {
    width: 100%;
    height: 100%;
  }
  .tools-bar {
    color: red;
    position: absolute;
    z-index: 999;
    top: 100px;
    left: 0;
    button {
      margin: 0 20px;
    }
  }
  .port-location-warp {
    position: absolute;
    width: 80px;
    height: 106px;
    // background: url("~@/assets/img/portalEntry/location_icon_1.png");
    background-size: 100% 100% !important;
    bottom: 0px;
    left: 0px;
    opacity: 1;
    pointer-events: all;
    transform: translate(-40px, 36px);
    cursor: pointer;
    &:hover {
      background: url("~@/assets/img/portalEntry/location_icon_hover.png") !important;
      background-size: 100% 100% !important;
    }
    &.hide {
      opacity: 0;
      pointer-events: none;
    }
    .name {
      position: absolute;
      font-size: 16px;
      color: #fff;
      padding: 6px 15px;
      background: rgba(22, 13, 1, 0.8);
      border-radius: 6px;
      white-space: nowrap;
      left: 64px;
      letter-spacing: 2px;
      top: 0;
      user-select: none;
    }
  }
  .config-manage-button {
    position: absolute;
    z-index: 9;
    top: 110px;
    right: 20px;
    width: 112px;
    height: 38px;
    background: url("~@/assets/img/portalEntry/peizhi.png");
    background-size: 100% 100%;
    display: flex;
    align-items: center;
    justify-content: center;
    cursor: pointer;
    border-radius: 19px;
    transition: 0.3s;
    &:hover {
      .config-menu {
        visibility: visible;
      }
    }
    &.hide {
      .config-menu {
        visibility: hidden;
      }
    }
    &:hover,
    &.active {
      background: url("~@/assets/img/portalEntry/peizhi-selected.png");
      background-size: 100% 100%;
    }
    .config-menu {
      position: absolute;
      width: 112px;
      background: rgba(3, 26, 44, 0.7);
      border-radius: 4px;
      left: 50%;
      transform: translateX(-50%);
      top: 38px;
      padding: 10px 0;
      visibility: hidden;
      .item {
        width: 112px;
        height: 32px;
        display: flex;
        align-items: center;
        justify-content: center;
        letter-spacing: 1px;
        &:hover,
        &.active {
          background: rgba(0, 213, 255, 0.3);
        }
      }
    }
    &.right {
      right: 330px;
    }
    &.right_2 {
      right: 346px;
    }
  }
  .port-area-container {
    position: absolute;
    top: 120px;
    left: 50%;
    transform: translateX(-50%);
    display: flex;
    align-items: center;
    .port-item {
      cursor: pointer;
      display: flex;
      flex-direction: column;
      align-items: center;
      margin-right: 100px;
      &:last-of-type {
        margin-right: 0;
      }
      .icon {
        width: 56px;
        height: 48px;
        background: url("~@/assets/img/portalEntry/icon_18.png");
        background-size: 100% 100%;
        margin-bottom: 6px;
      }
      .name {
        font-family: Microsoft YaHei;
        font-weight: 400;
        font-size: 14px;
        color: #8ffce6;
      }
      &.active-port {
        .icon {
          background: url("~@/assets/img/portalEntry/icon_19.png");
          background-size: 100% 100%;
        }
        .name {
          color: #eef9ff;
        }
      }
    }
  }

  .dock-plan-warp {
    position: absolute;
    width: 194px;
    background: rgba(3, 26, 44, 0.7);
    border: 1px solid #2e70a7;
    border-radius: 0 0 4px 4px;
    top: 110px;
    right: 126px;
    border-top: 3px solid #00fffc;
    padding: 12px 24px 0 24px;
    transition: 0.3s;
    z-index: 9;
    user-select: none;
    &.hide {
      right: -260px;
    }
    &.right {
      right: 20px;
    }
    &.left {
      right: 330px !important;
    }
    &.right-max {
      right: 432px !important;
    }
    .plan-item {
      display: flex;
      align-items: center;
      color: #8fdbfc;
      font-size: 14px;
      &:not(:last-child) {
        margin-bottom: 10px;
      }
      &::before {
        content: "";
        display: flex;
        width: 16px;
        height: 10px;
        margin-right: 12px;
      }
      &:nth-child(1) {
        &::before {
          background: rgba(248, 176, 108, 0.5);
          border: 1px solid #f8b06c;
        }
      }
      &:nth-child(2) {
        &::before {
          background: rgba(0, 221, 255, 0.5);
          border: 1px solid #00ddff;
        }
      }
      &:nth-child(3) {
        &::before {
          background: rgba(163, 144, 218, 0.5);
          border: 1px solid #a390da;
        }
      }
      &:nth-child(4) {
        &::before {
          background: rgba(246, 129, 112, 0.5);
          border: 1px solid #f68170;
        }
      }
      &:nth-child(5) {
        &::before {
          background: rgba(86, 148, 225, 0.5);
          border: 1px solid #5694e1;
        }
      }
      &:nth-child(6) {
        &::before {
          background: rgba(127, 234, 155, 0.5);
          border: 1px solid #7fea9b;
        }
      }
    }

    /deep/.ant-checkbox-wrapper {
      margin-left: 0;
      margin-bottom: 12px;
      span:nth-child(2) {
        color: #8fdbfc;
        font-size: 14px;
      }
      .ant-checkbox {
        .ant-checkbox-inner {
          background: rgba(0, 144, 255, 0.2);
          border: 1px solid #0090ff;
          border-radius: 2px;
        }
        &.ant-checkbox-checked {
          .ant-checkbox-inner {
            background: #26ffab;
            border: 1px solid #26ffab;
            &::after {
              border-color: #00316c;
            }
          }
        }
        &.ant-checkbox-indeterminate {
          .ant-checkbox-inner {
            border: 1px solid #26ffab;
            &:after {
              background: #26ffab;
            }
          }
        }
      }
    }
  }
  .bim-tool-bar {
    width: 130px;
    height: 34px;
    background: url("~@/assets/img/portalEntry/icon_17.png");
    background-size: 100% 100%;
    cursor: pointer;
    bottom: 40px;
    right: 20px;
    z-index: 9999;
    position: absolute;
    transition: 0.3s;
    color: #eef9ff;
    font-size: 14px;
    display: flex;
    align-items: center;
    box-sizing: border-box;
    padding-left: 22px;
    color: #b8f3ff;
    /deep/.ant-switch {
      min-width: 32px;
      width: 32px;
      height: 14px;
      margin-left: 10px;
      &.ant-switch-checked {
        background: rgba(0, 255, 255, 0.7) !important;
        border: 1px solid #00ffff;
      }
      &::after {
        width: 10px;
        height: 10px;
      }
    }
  }
  .config-panel-container {
    width: 300px;
    height: 100%;
    position: absolute;
    z-index: 9;
    top: 0;
    right: -300px;
    box-sizing: border-box;
    padding: 110px 0 80px 0;
    transition: 0.3s;
    &.show {
      right: 20px;
    }
    .body {
      width: 100%;
      height: 100%;
      display: flex;
      flex-direction: column;
      .header {
        height: 36px;
        width: 312px;
        background: url("~@/assets/img/portalEntry/icon_4.png");
        background-size: 100% 100%;
        position: relative;
        color: #eefaff;
        font-size: 16px;
        box-sizing: border-box;
        padding: 4px 0 0 44px;
        .close {
          cursor: pointer;
          width: 26px;
          height: 26px;
          position: absolute;
          top: 0;
          right: 0;
          border-radius: 50%;
        }
      }
      .content {
        flex: 1;
        background: url("~@/assets/img/portalEntry/icon_5.png");
        background-size: 100% 100%;
        overflow: hidden;
      }
    }
  }

  .elem-list-warp {
    position: absolute;
    top: 0;
    left: 20px;
    height: 100%;
    z-index: 9;
    user-select: none;
    transition: 0.3s;
    width: 382px;

    .visible-button {
      display: flex;
      align-items: center;
      justify-content: center;
      color: #f4ffff;
      font-size: 16px;
      cursor: pointer;
      flex-direction: column;
      position: absolute;
      top: 50%;
      transform: translateY(-50%);
      z-index: 9999;
      right: -36px;
      .button-item {
        width: 47px;
        height: 160px;
        writing-mode: vertical-rl;
        display: flex;
        align-items: center;
        justify-content: center;
        background: url("~@/assets/img/portalEntry/icon_1.png");
        background-size: 100% 100%;
        span {
          margin-right: 8px;
        }
        &:not(:first-child) {
          margin-top: 15px;
        }
        &.active {
          background: url("~@/assets/img/portalEntry/icon_2.png");
          background-size: 100% 100%;
        }
      }
    }
    &.hide {
      left: -382px;
      .visible-button {
        right: -46px;
      }
    }
    .tree-card {
      width: 382px;
      height: 640px;
      flex: 1;
      display: flex;
      flex-direction: column;
      transition: 0.3s;
      top: 130px;
      position: absolute;
      background: url("~@/assets/img/portalEntry/icon_3.png");
      background-size: 100% 100%;
      overflow: hidden;
      .close-button {
        position: absolute;
        width: 26px;
        height: 26px;
        border-radius: 50%;
        top: 0px;
        right: 0px;
        cursor: pointer;
      }
      &.hide {
        margin-left: -440px;
      }

      .header {
        height: 40px;
        display: flex;
        color: #eefaff;
        font-size: 20px;
        box-sizing: border-box;
        padding-left: 48px;
        line-height: 38px;
        flex-shrink: 0;
      }
      .body {
        width: 370px;
        flex: 1;
        overflow: hidden;
        box-sizing: border-box;
        margin-bottom: 6px;
        display: flex;
        flex-direction: column;
        .condition-warp {
          flex-shrink: 0;
          display: flex;
          padding: 12px 16px;
          box-sizing: border-box;
          justify-content: space-between;
          /deep/.ant-select {
            .ant-select-selection {
              background: rgba(0, 213, 255, 0.1);
              border: 1px solid #00d5ff;
              color: #e0f8ff;
              font-size: 14px;
              .ant-select-selection__placeholder {
                color: #b8e8ff;
              }
              .ant-select-arrow {
                color: #b8e8ff;
              }
              .ant-select-selection__clear {
                background: none;
                .anticon {
                  background: #fff;
                  border-radius: 50%;
                  color: #b8e8ff;
                }
              }
            }
          }
        }
        .condition-body {
          flex: 1;
          padding: 0 16px;
          .custom-scrollbar();
          box-sizing: border-box;
          margin-bottom: 12px;
        }
      }
    }
  }
  .monitor-legend {
    position: absolute;
    right: 40px;
    bottom: 50px;
    transition: 0.3s;
    z-index: 9;
    .legend-item {
      color: #8fdbfc;
      font-size: 16px;
      display: flex;
      align-items: center;
      &:not(:last-child) {
        margin-bottom: 16px;
      }
      &::before {
        display: flex;
        content: "";
        width: 26px;
        height: 24px;
        margin-right: 10px;
      }
      &:nth-child(1) {
        &::before {
          background: url("~@/assets/img/portalEntry/modal_icon_9.png");
          background-size: 100% 100%;
        }
      }
      &:nth-child(2) {
        &::before {
          background: url("~@/assets/img/portalEntry/modal_icon_10.png");
          background-size: 100% 100%;
        }
      }
      &:nth-child(3) {
        &::before {
          background: url("~@/assets/img/portalEntry/modal_icon_11.png");
          background-size: 100% 100%;
        }
      }
    }
    &.hide {
      right: -100px;
    }
  }
  .gis-layer-bg {
    position: absolute;
    width: 100%;
    height: 100%;
    background: url("~@/assets/img/portalEntry/modal_icon_18.png");
    background-size: 100% 100%;
    top: 0;
    left: 0;
    pointer-events: none;
  }
}
/deep/.editorGis-drawer-warp {
}
</style>
